<!-- autoindex for nginx, see https://phuslu.github.io -->
<!-- nginx 索引美化 基于 https://phuslu.github.io 优化，增加了按文件名、日期、大小排序的功能 -->
<!-- add_after_body /autoindex.html; -->
<script>
    function switchMonth(month) {
        switch (month) {
            case 'Jan':
                return 0;
            case 'Feb':
                return 1;
            case 'Mar':
                return 2;
            case 'Apr':
                return 3;
            case 'May':
                return 4;
            case 'Jun':
                return 5;
            case 'Jul':
                return 6;
            case 'Aug':
                return 7;
            case 'Sept':
                return 8;
            case 'Oct':
                return 9;
            case 'Nov':
                return 10;
            case 'Dec':
                return 11;
            default:
                return month
        }
    }

    !function () {
        let website_title = '';
        let datetime_format = '%d-%b-%Y %H:%M';
        let show_readme_md = true;
        let max_name_length = 50;

        let dom = {
            element: null,
            get: function (o) {
                let obj = Object.create(this);
                obj.element = (typeof o == "object") ? o : document.createElement(o);
                return obj;
            },
            add: function (o) {
                let obj = dom.get(o);
                this.element.appendChild(obj.element);
                return obj;
            },
            text: function (t) {
                this.element.appendChild(document.createTextNode(t));
                return this;
            },
            html: function (s) {
                this.element.innerHTML = s;
                return this;
            },
            attr: function (k, v) {
                this.element.setAttribute(k, v);
                return this;
            }
        };

        if (!document.head) return;
        head = dom.get(document.head);
        head.add('meta').attr('charset', 'utf-8');
        head.add('meta').attr('name', 'viewport').attr('content', 'width=device-width,initial-scale=1')

        if (!document.title) {
            document.write(["<div class=\"container\">",
                "<h3>nginx.conf</h3>",
                "<textarea rows=8 cols=50>",
                "# download autoindex.html to /wwwroot",
                "location ~ ^(.*)/$ {",
                "    charset utf-8;",
                "    autoindex on;",
                "    autoindex_localtime on;",
                "    autoindex_exact_size off;",
                "    add_after_body /autoindex.html;",
                "}",
                "</textarea>",
                "</div>"].join("\n"));
            return
        }

        let bodylines = document.body.innerHTML.split('\n');
        document.body.innerHTML = '';

        let subLocation = location.pathname.replace(document.title.replace('Index of ',''),'')
        let titlehtml = document.title.replace(/\/$/, '').split('/').slice(1).reduce(function (acc, v, i, a) {
          // return acc + '<a href="/' + a.slice(0, i + 1).join('/') + '/">' + v + '</a>/'
          return `${acc}<a href="${subLocation !== '' ? subLocation + '/' : '/'}${a.slice(0, i + 1).join('/')}/">${v}</a>/`
        }, 'Index of /');
        if (website_title) {
            document.title = website_title + ' - ' + document.title
        }

        div = dom.get('div').attr('class', 'container');
        div.add('table').add('tbody').add('tr').add('th').html(titlehtml);
        tbody = div.add('table').attr('class', 'table-hover').add('tbody');

        let insert = function (filename, datetime, size) {
            if (/\/$/.test(filename)) {
                css = 'file-directory'
            } else if (/\.(zip|7z|bz2|gz|tar|tgz|tbz2|cab)$/.test(filename)) {
                css = 'file-zip'
            } else if (/\.(jpg|png|bmp|gif|ico|webp)$/.test(filename)) {
                css = 'file-media'
            } else if (/\.(flv|mp4|avi|mkv|vp9)$/.test(filename)) {
                css = 'device-camera-video'
            } else {
                css = 'file'
            }

            displayname = decodeURIComponent(filename.replace(/\/$/, ''));
            if (displayname.length > max_name_length)
                displayname = displayname.substring(0, max_name_length - 3) + '..>';

            if (!isNaN(Date.parse(datetime))) {
                d = new Date(datetime);
                pad = function (s) {
                    return s < 10 ? '0' + s : s
                };
                mon = function (m) {
                    return ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'][m]
                };
                datetime = datetime_format
                    .replace('%Y', d.getFullYear())
                    .replace('%m', pad(d.getMonth() + 1))
                    .replace('%d', pad(d.getDate()))
                    .replace('%H', pad(d.getHours()))
                    .replace('%M', pad(d.getMinutes()))
                    .replace('%S', pad(d.getSeconds()))
                    .replace('%b', mon(d.getMonth()))
            }

            tr = tbody.add('tr');
            tr.add('td').add('a').attr('class', 'octicon ' + css).attr('href', filename).text(displayname);
            tr.add('td').text(datetime);
            tr.add('td').text(size)
        };

        let readme = '';
        let mdFiles = [];
        tr = tbody.add('tr');
        tr.add('td').add('a').attr('class', 'sortBy').attr('id', 'sortByName').attr('href', '#').text('File Name ').add('span').text('↓');
        tr.add('td').add('a').attr('class', 'sortBy').attr('id', 'sortByDate').attr('href', '#').text('Date ').add('span').text('↓');
        tr.add('td').add('a').attr('class', 'sortBy').attr('id', 'sortBySize').attr('href', '#').text('Size ').add('span').text('↓');
        insert('../', '', '-');
        for (let i in bodylines) {
            if ((m = /\s*<a href="(.+?)">(.+?)<\/a>\s+(\S+)\s+(\S+)\s+(\S+)\s*/.exec(bodylines[i]))) {
                filename = m[1];
                datetime = m[3] + ' ' + m[4];
                size = m[5];
                insert(filename, datetime, size);
                if (filename.toLowerCase() === 'readme.md') {
                    readme = filename
                }
                if (filename.includes('.md')) {
                    mdFiles.push(filename);
                }
            }
        }

        document.body.appendChild(div.element);

        if ((show_readme_md && readme !== '') || mdFiles.length !== 0) {
            if (readme === '') {
                readme = mdFiles[0];
                mdFiles.splice(mdFiles.indexOf(readme), 1);
            } else {
                mdFiles.splice(mdFiles.indexOf(readme), 1);
            }

            tbody = div.add('table').add('tbody');
            let mdTh = tbody.add('tr').add('th').add('select');
            mdTh.attr('id', 'mdSelect').add('option').attr('value', readme).text(readme);
            for (let mdFile of mdFiles) {
                mdTh.add('option').attr('value', mdFile).text(mdFile);
            }
            let mdSelect = document.getElementById('mdSelect');
            mdSelect.onchange = function () {
                let mdFileName = mdSelect.options[mdSelect.selectedIndex].value;
                let xhr = new XMLHttpRequest();
                xhr.open('GET', location.pathname + mdFileName, true);
                xhr.onload = function () {
                    if (xhr.status >= 200 && xhr.status < 400) {
                        wait = function (name, callback) {
                            let interval = 10; // ms
                            window.setTimeout(function () {
                                if (window[name]) {
                                    callback(window[name])
                                } else {
                                    window.setTimeout(arguments.callee, interval)
                                }
                            }, interval)
                        };
                        wait('marked', function () {
                            document.getElementById("readme").innerHTML = marked(xhr.responseText)
                        })
                    }
                };
                xhr.send();
            };

            tbody.add('tr').add('td').add('div').attr('id', 'readme').attr('class', 'markdown-body');

            let xhr = new XMLHttpRequest();
            xhr.open('GET', location.pathname + readme, true);
            xhr.onload = function () {
                if (xhr.status >= 200 && xhr.status < 400) {
                    wait = function (name, callback) {
                        let interval = 10; // ms
                        window.setTimeout(function () {
                            if (window[name]) {
                                callback(window[name])
                            } else {
                                window.setTimeout(arguments.callee, interval)
                            }
                        }, interval)
                    };
                    wait('marked', function () {
                        document.getElementById("readme").innerHTML = marked(xhr.responseText)
                    })
                }
            };
            xhr.send();

            div.add('script').attr('src', 'https://cdn.jsdelivr.net/npm/marked');
            div.add('link').attr('rel', 'stylesheet').attr('href', 'https://cdn.jsdelivr.net/npm/github-markdown-css')
        }
        let oTable = document.getElementsByClassName('table-hover')[0];
        let oTbody = oTable.tBodies[0];
        let trArray = [];//用来存放每一个tr
        let isAsc = true;//用来判断升序，还是降序
        for (let i = 0; i < oTbody.rows.length - 2; i++) {
            trArray[i] = oTbody.rows[i + 2];//这里是把每一个tr存放到一个数组，而不是排序的依据（这里是cells[0].innerHTML）
        }
        let sortByNameATag = document.getElementById('sortByName');
        sortByNameATag.onclick = function () {
            trArray.sort(function (td1, td2) {
                if (isAsc) {
                    return td1.cells[0].innerText.localeCompare(td2.cells[0].innerText);
                } else {
                    return td2.cells[0].innerText.localeCompare(td1.cells[0].innerText);
                }

            });
            isAsc = !isAsc;
            let upDownSymbol = sortByNameATag.getElementsByTagName('span')[0];
            if (upDownSymbol.innerText === '↑') {
                upDownSymbol.innerText = '↓';
            } else {
                upDownSymbol.innerText = '↑';
            }
            let oFragment = document.createDocumentFragment(); //创建文档碎片
            for (let j = 0; j < trArray.length; j++) {
                oFragment.appendChild(trArray[j]);
            }
            oTable.appendChild(oFragment);
        };
        let sortByDateATag = document.getElementById('sortByDate');
        sortByDateATag.onclick = function () {
            trArray.sort(function (td1, td2) {
                let datestr1 = td1.cells[1].innerText;
                let day1 = parseInt(datestr1.split('-')[0]);
                let month1 = switchMonth(datestr1.split('-')[1]);
                let year1 = parseInt(datestr1.split('-')[2]);
                let hour1 = parseInt(datestr1.split(' ')[1].split(':')[0]);
                let minute1 = parseInt(datestr1.split(' ')[1].split(':')[1]);
                let date1 = new Date(year1, month1, day1, hour1, minute1, 0, 0);

                let datestr2 = td2.cells[1].innerText;
                let day2 = parseInt(datestr2.split('-')[0]);
                let month2 = switchMonth(datestr2.split('-')[1]);
                let year2 = parseInt(datestr2.split('-')[2]);
                let hour2 = parseInt(datestr2.split(' ')[1].split(':')[0]);
                let minute2 = parseInt(datestr2.split(' ')[1].split(':')[1]);
                let date2 = new Date(year2, month2, day2, hour2, minute2, 0, 0);

                if (isAsc) {
                    return date1.getTime() - date2.getTime();
                } else {
                    return date2.getTime() - date1.getTime();
                }
            });
            isAsc = !isAsc;
            let upDownSymbol = sortByDateATag.getElementsByTagName('span')[0];
            if (upDownSymbol.innerText === '↑') {
                upDownSymbol.innerText = '↓';
            } else {
                upDownSymbol.innerText = '↑';
            }
            let oFragment = document.createDocumentFragment(); //创建文档碎片
            for (let j = 0; j < trArray.length; j++) {
                oFragment.appendChild(trArray[j]);
            }
            oTable.appendChild(oFragment);
        };
        let sortBySizeATag = document.getElementById('sortBySize');
        sortBySizeATag.onclick = function () {
            trArray.sort(function (td1, td2) {
                let td1InnerText = td1.cells[2].innerText;
                let td2InnerText = td2.cells[2].innerText;
                if (td1InnerText === '-') {
                    td1InnerText = -1;
                }
                if (td2InnerText === '-') {
                    td2InnerText = -1;
                }
                if (td1InnerText.toString().includes('M')) {
                    td1InnerText = parseInt(td1InnerText.substring(0, td1InnerText.indexOf('M'))) * 1024 * 1024;
                }
                if (td1InnerText.toString().includes('K')) {
                    td1InnerText = parseInt(td1InnerText.substring(0, td1InnerText.indexOf('K'))) * 1024;
                }
                if (td2InnerText.toString().includes('M')) {
                    td2InnerText = parseInt(td2InnerText.substring(0, td2InnerText.indexOf('M'))) * 1024 * 1024;
                }
                if (td2InnerText.toString().includes('K')) {
                    td2InnerText = parseInt(td2InnerText.substring(0, td2InnerText.indexOf('K'))) * 1024;
                }
                if (isAsc) {
                    return parseInt(td1InnerText) - parseInt(td2InnerText);
                } else {
                    return parseInt(td2InnerText) - parseInt(td1InnerText);
                }

            });
            isAsc = !isAsc;
            let upDownSymbol = sortBySizeATag.getElementsByTagName('span')[0];
            if (upDownSymbol.innerText === '↑') {
                upDownSymbol.innerText = '↓';
            } else {
                upDownSymbol.innerText = '↑';
            }
            for (let j = 0; j < trArray.length; j++) {
                oTbody.appendChild(trArray[j]);
            }
        };
    }()
</script>
<!-- autoindex for nginx, see https://phuslu.github.io -->

<style>
    body {
        margin: 0;
        font-family: "ubuntu", "Tahoma", "Microsoft YaHei", Arial, Serif, serif;
    }

    .container {
        padding-right: 15px;
        padding-left: 15px;
        margin-right: auto;
        margin-left: auto;
    }

    @media (min-width: 768px) {
        .container {
            max-width: 750px;
        }
    }

    @media (min-width: 992px) {
        .container {
            max-width: 970px;
        }
    }

    @media (min-width: 1200px) {
        .container {
            max-width: 1170px;
        }
    }

    table {
        width: 100%;
        max-width: 100%;
        margin-bottom: 20px;
        border: 1px solid #ddd;
        padding: 0;
        border-collapse: collapse;
    }

    table th {
        font-size: 14px;
    }

    table tr {
        border: 1px solid #ddd;
        padding: 5px;
    }

    table tr:nth-child(odd) {
        background: #f9f9f9
    }

    table th, table td {
        border: 1px solid #ddd;
        font-size: 14px;
        line-height: 20px;
        padding: 3px;
        text-align: left;
    }

    a {
        color: #337ab7;
        text-decoration: none;
    }

    a:hover, a:focus {
        color: #2a6496;
        text-decoration: underline;
    }

    table.table-hover > tbody > tr:hover > td,
    table.table-hover > tbody > tr:hover > th {
        background-color: #f5f5f5;
    }

    .markdown-body {
        margin: 10px 32px;
        float: left;
        font-family: "ubuntu", "Tahoma", "Microsoft YaHei", Arial, Serif, serif;
    }

    /* octicons */
    .octicon {
        background-position: center left;
        background-repeat: no-repeat;
        padding-left: 16px;
    }

    .sortBy {
        color: #5f5f5f;
        text-decoration: none;
        font-weight: bold;
        font-size: 16px;
    }

    .file {
        background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='16' viewBox='0 0 12 16'%3E%3Cpath d='M6 5L2 5 2 4 6 4 6 5 6 5ZM2 8L9 8 9 7 2 7 2 8 2 8ZM2 10L9 10 9 9 2 9 2 10 2 10ZM2 12L9 12 9 11 2 11 2 12 2 12ZM12 4.5L12 14C12 14.6 11.6 15 11 15L1 15C0.5 15 0 14.6 0 14L0 2C0 1.5 0.5 1 1 1L8.5 1 12 4.5 12 4.5ZM11 5L8 2 1 2 1 14 11 14 11 5 11 5Z' fill='%237D94AE'/%3E%3C/svg%3E");
    }

    .file-directory {
        background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='14' height='16' viewBox='0 0 14 16'%3E%3Cpath d='M13 4L7 4 7 3C7 2.3 6.7 2 6 2L1 2C0.5 2 0 2.5 0 3L0 13C0 13.6 0.5 14 1 14L13 14C13.6 14 14 13.6 14 13L14 5C14 4.5 13.6 4 13 4L13 4ZM6 4L1 4 1 3 6 3 6 4 6 4Z' fill='%237D94AE'/%3E%3C/svg%3E");
    }

    .file-media {
        background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='16' viewBox='0 0 12 16'%3E%3Cpath d='M6 5L8 5 8 7 6 7 6 5 6 5ZM12 4.5L12 14C12 14.6 11.6 15 11 15L1 15C0.5 15 0 14.6 0 14L0 2C0 1.5 0.5 1 1 1L8.5 1 12 4.5 12 4.5ZM11 5L8 2 1 2 1 13 4 8 6 12 8 10 11 13 11 5 11 5Z' fill='%237D94AE'/%3E%3C/svg%3E");
    }

    .device-camera-video {
        background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='16' height='16' viewBox='0 0 16 16'%3E%3Cpath d='M15.2,2.09 L10,5.72 L10,3 C10,2.45 9.55,2 9,2 L1,2 C0.45,2 0,2.45 0,3 L0,12 C0,12.55 0.45,13 1,13 L9,13 C9.55,13 10,12.55 10,12 L10,9.28 L15.2,12.91 C15.53,13.14 16,12.91 16,12.5 L16,2.5 C16,2.09 15.53,1.86 15.2,2.09 L15.2,2.09 Z' fill='%237D94AE' /%3E%3C/svg%3E");
    }

    .file-zip {
        background-image: url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='16' viewBox='0 0 12 16'%3E%3Cpath d='M8.5 1L1 1C0.4 1 0 1.4 0 2L0 14C0 14.6 0.4 15 1 15L11 15C11.6 15 12 14.6 12 14L12 4.5 8.5 1ZM11 14L1 14 1 2 4 2 4 3 5 3 5 2 8 2 11 5 11 14 11 14ZM5 4L5 3 6 3 6 4 5 4 5 4ZM4 4L5 4 5 5 4 5 4 4 4 4ZM5 6L5 5 6 5 6 6 5 6 5 6ZM4 6L5 6 5 7 4 7 4 6 4 6ZM5 8L5 7 6 7 6 8 5 8 5 8ZM4 9.3C3.4 9.6 3 10.3 3 11L3 12 7 12 7 11C7 9.9 6.1 9 5 9L5 8 4 8 4 9.3 4 9.3ZM6 10L6 11 4 11 4 10 6 10 6 10Z' fill='%237D94AE'/%3E%3C/svg%3E");
    }
</style>

